<!DOCTYPE html>
<html lang="zh-cn">
<head>
    <meta charset="UTF-8">
    <title>Title</title>
</head>
<body>
<script>
// 寄生组合式继承

// 父类 人
function Person(name = 'hello', age = 18) {
    // 实例的属性
    this.name = name
    this.age = age
}

// 原型的属性和方法
Person.prototype.country = 'China'
Person.prototype.sayName = function () {
    console.log(this.name)
}

// 子类 男人
function Man(name, age) {
    // new Man() 不传任何参数，name, age 值为 undefined，但神奇的是并不会替换 Person 函数的参数默认值
    // 使用 call 将 this 替换为 new Man()，继承 Person 实例对象的属性
    Person.call(this, name, age)
    this.gender = 'male'
}

(function () {
    function Super() {
    }

    // 为什么不直接用 Man.prototype = new Person()，因为这样会调用两次 父类构造函数，第一次在 Person.call()
    // 通过将 父类的原型 复制出来，避免调用两次，强迫症患者放下手中的刀
    Super.prototype = Person.prototype
    Man.prototype = new Super()
})()

// 子类的原型属性或方法
Man.prototype.height = 180
Man.prototype.sayGender = function () {
    console.log(this.gender)
}
// 将子类的原型对象的构造函数指向设为子类
Man.prototype.constructor = Man

const man = new Man('ManName', 18)
console.log(man);
</script>
</body>
</html>
